using System.Collections.Generic;
using NUnit.Framework;
using ValidationFramework.Reflection;

namespace ValidationFramework.Tests
{
    public class ValidatableRuleTest
    {

        public class ClassNotIValidatable 
        {
            [RequiredStringRule]
            public string PropertyToValidate { get; set; }
        }
        public class ClassIsIValidatable : IValidatable
        {
            public bool IsValid
            {
                get
                {
                    return true;
                }
            }

            public IList<string> ErrorMessages
            {
                get
                {
                    return null;
                }
            }
        }

        const string expectedErrorMessage = "expectedErrorMessage";
        const string expectedRuleSet = "EXPECTEDRULESET";

        [TestFixture]
        public class Construction
        {
            [Test]
            public void Constructor1()
            {
                var rule = new ValidatableRule();
                Assert.IsFalse(rule.UseMemberErrorMessages);
            }


            [Test]
            public void Constructor2()
            {
                var rule = new ValidatableRule();
                Assert.IsFalse(rule.UseMemberErrorMessages);
            }


            [Test]
            public void Constructor3()
            {
                var rule = new ValidatableRule();
                Assert.IsNull(rule.ErrorMessage);
                Assert.IsFalse(rule.UseErrorMessageProvider);
            }
        }


        [TestFixture]
        public class IsEquivalent
        {
            [Test]
            public void Simple()
            {
                var rule1 = new ValidatableRule();
                var rule2 = new ValidatableRule();

                Assert.IsTrue(rule1.IsEquivalent(rule2));
            }
        }


        [TestFixture]
        public class RuleInterpretation
        {
            [Test]
            public void RuleRuleInterpretation()
            {
                var rule = new ValidatableRule();
                Assert.IsNotNull(rule.RuleInterpretation);
            }
        }


        [TestFixture]
        public class Validate
        {
            [Test]
            public void ImplimentingIValidatable()
            {

                var rule = new ValidatableRule();
                Assert.IsNull(rule.BaseValidate(null, null, null, null));

                var value = new ClassIsIValidatable();
                Assert.IsNull(rule.BaseValidate(null, value, null, null));
            }
            [Test]
            public void NotImplimentingIValidatable()
            {

                var rule = new ValidatableRule();
                Assert.IsNull(rule.BaseValidate(null, null, null, null));

                var value = new ClassNotIValidatable();
                InfoDescriptor infoDescriptor = new MockInfoDescriptor();
                infoDescriptor.Rules.Add(rule);
                Assert.IsNotNull(rule.BaseValidate(null, value, null, infoDescriptor));
            }

        }


        [TestFixture]
        public class CheckTypes
        {
            [Test]
            public void Simple()
            {
                var rule = new ValidatableRule();
                rule.CheckType(new MockInfoDescriptor(typeof (ClassIsIValidatable).TypeHandle, "foo"));
            }


            //[Test]
            //[ExpectedException(typeof(ArgumentException), ExpectedMessage = "Member 'foo' must be a 'ValidationFramework.IValidatable' to be used for the ValidationFramework.ValidatableRule. Actual Type 'System.Int32'.\r\nParameter name: value")]
            //public void ExceptionInvalidType()
            //{
            //    new ValidatableRule(null, null, false)
            //        {
            //            rule.CheckType(new MockInfoDescriptor(TypePointers.IntTypeHandle, "foo")
            //        };
            //}
        }

    }
}